home *** CD-ROM | disk | FTP | other *** search
/ BCI NET 2 / BCI NET 2.iso / archives / programming / source / tracker-4.13.lha / tracker / Amiga / scroll_window.c < prev    next >
Encoding:
C/C++ Source or Header  |  1995-02-14  |  6.2 KB  |  230 lines

  1. /* amiga/scroll_window.c 
  2.     vi:ts=3 sw=3:
  3.  */
  4.  
  5. /* $Id: scroll_window.c,v 1.3 1995/02/14 16:51:22 espie Exp espie $
  6.  * $Log: scroll_window.c,v $
  7.  * Revision 1.3  1995/02/14  16:51:22  espie
  8.  * *** empty log message ***
  9.  *
  10.  * Revision 1.2  1995/02/13  22:05:42  espie
  11.  * The display takes more space taken into account.
  12.  *
  13.  * Revision 1.1  1995/01/13  13:31:35  espie
  14.  * Initial revision
  15.  *
  16.  * Revision 1.4  1994/01/09  04:49:18  Espie
  17.  * Stupid: forgot that a window font can very well be proportional.
  18.  * It's easier to rely on GfxBase->DefaultFont after all.
  19.  * Uncentralized event handling using event management functions.
  20.  * Handle own's clipping without Layers.
  21.  * Use dynamic colours/masks according to current screen.
  22.  * Added forbid_reopen to avoid dangling window.
  23.  *
  24.  */
  25.  
  26. /* The line scroller implemented as a window */
  27.  
  28. #include <assert.h>
  29.  
  30. #include <intuition/screens.h>
  31. #include <graphics/text.h>
  32. #include <graphics/gfxmacros.h>
  33. #include <proto/intuition.h>
  34. #include <proto/exec.h>
  35. #include <proto/graphics.h>
  36. #include <graphics/gfxbase.h>
  37.  
  38. #include "defs.h"
  39. #include "extern.h"
  40. #include "amiga/amiga.h"
  41. #include "prefs.h"
  42.  
  43. ID("$Id: scroll_window.c,v 1.3 1995/02/14 16:51:22 espie Exp espie $")
  44.  
  45. LOCAL void init_scroller(void);
  46. LOCAL void (*INIT)(void) = init_scroller;
  47. LOCAL int forbid_reopen = FALSE;
  48. LOCAL void handle_scroller(GENERIC nothing);
  49.  
  50. XT struct IntuitionBase *IntuitionBase;
  51. XT struct GfxBase *GfxBase;
  52.  
  53. LOCAL struct Screen *pubscreen;
  54.  
  55. /* our window */
  56. LOCAL struct Window *scroll_win = 0;
  57. LOCAL struct TextFont *font;
  58.    
  59.  
  60. /* to build up write masks */
  61. LOCAL ULONG text, highlight, background;
  62.  
  63.  
  64. LOCAL void close_scroller()    
  65.    {
  66.    if (scroll_win)
  67.       {
  68.       remove_signal_handler(scroll_win->UserPort->mp_SigBit);
  69.       CloseWindow(scroll_win);
  70.       }
  71.    scroll_win = 0;               /* and get ready for reopen */
  72.    }
  73.  
  74. LOCAL void really_close_scroller()
  75.    {
  76.    forbid_reopen = TRUE;
  77.    close_scroller();
  78.    }
  79.  
  80. /* graphic niceties: draw vertical lines at the right separation points
  81.  * all the way between y1 and the bottom
  82.  */
  83. LOCAL void separation_lines(int y1)
  84.    {
  85.    int x, xs, i, c;
  86.    
  87.    xs = font->tf_XSize;
  88.    
  89.    SetWrMsk(scroll_win->RPort, background | highlight);  
  90.    SetAPen(scroll_win->RPort, highlight);   
  91.    x = scroll_win->BorderLeft;
  92.    for (i = 1; i < 5; i++)
  93.       {
  94.       if (i == 3)
  95.          x+= xs;
  96.       else
  97.          x += 14 * xs;     /* 14 chars per column */
  98.       c = x - xs/2;
  99.       if (c >= scroll_win->Width - scroll_win->BorderRight -1)
  100.          break;
  101.       Move(scroll_win->RPort, x - xs/2, y1);
  102.       Draw(scroll_win->RPort, x - xs/2, scroll_win->Height - scroll_win->BorderBottom - 1);
  103.       }
  104.    }
  105.    
  106. LOCAL void init_scroller()
  107.    {
  108.    struct DrawInfo *dr;
  109.    
  110.    at_end(really_close_scroller);
  111.       /* default text, background, etc */
  112.    text = 1;
  113.    background = 0;
  114.    highlight = 7;
  115.    pubscreen = obtain_pubscreen();
  116.    dr = GetScreenDrawInfo(pubscreen);
  117.    if (dr)
  118.       {
  119.       if (dr->dri_Version >= 1)  /* for V 2.04 */
  120.          {
  121.          text = dr->dri_Pens[TEXTPEN];
  122.          background = dr->dri_Pens[BACKGROUNDPEN];
  123.          highlight = dr->dri_Pens[SHINEPEN];
  124.          }
  125.       FreeScreenDrawInfo(pubscreen, dr);
  126.       }
  127.    }
  128.    
  129.  
  130. LOCAL void open_scroller()
  131.    {
  132.    INIT_ONCE;
  133.    font = GfxBase->DefaultFont;
  134.    scroll_win = OpenWindowTags(NULL,
  135.       WA_Title, "Scroll",
  136.       WA_DepthGadget, TRUE,
  137.       WA_SmartRefresh, TRUE,
  138.       WA_DragBar, TRUE,
  139.       WA_SizeGadget, TRUE,
  140.       WA_CloseGadget, TRUE,
  141.       WA_InnerWidth, font->tf_XSize * 60, /* 60 = 14 * 4 + some margin */
  142.       WA_InnerHeight, font->tf_YSize * 15,
  143.       WA_MinWidth, 15 * font->tf_XSize,
  144.       WA_MaxWidth, ~0,           /* need some room for the size gadget */
  145.       WA_MinHeight, 2 * pubscreen->WBorTop,   
  146.       WA_MaxHeight, ~0,
  147.       WA_AutoAdjust, TRUE,
  148.       WA_NoCareRefresh, TRUE,
  149.       WA_PubScreen, pubscreen,
  150.       WA_IDCMP, IDCMP_NEWSIZE | IDCMP_CLOSEWINDOW,
  151.       TAG_END);
  152.  
  153.    if (!scroll_win)
  154.       end_all(0);
  155.       
  156.    SetFont(scroll_win->RPort, font);
  157.    install_signal_handler(scroll_win->UserPort->mp_SigBit, handle_scroller, 0);
  158.    separation_lines(scroll_win->BorderTop);
  159.    }
  160.  
  161.  
  162.  
  163. LOCAL void handle_scroller(GENERIC nothing)   
  164.    {
  165.    struct IntuiMessage *msg;
  166.    while (scroll_win && (msg = GetMsg(scroll_win->UserPort)))
  167.       switch(msg->Class)
  168.          {
  169.       case IDCMP_NEWSIZE:
  170.          ReplyMsg(msg);
  171.          separation_lines(scroll_win->BorderTop);  /* redraw lines where applicable */
  172.          break;
  173.       case IDCMP_SIZEVERIFY:
  174.          ReplyMsg(msg);
  175.          break;
  176.       case IDCMP_CLOSEWINDOW:
  177.          ReplyMsg(msg);
  178.          close_scroller();
  179.          set_pref_scalar(PREF_SHOW, FALSE);
  180.          break;
  181.       default:
  182.          ReplyMsg(msg);
  183.          }
  184.    }
  185.  
  186. void add_scroller(char *s)
  187.    {
  188.    int max_length;
  189.  
  190.    if (forbid_reopen)
  191.       return;
  192.    if (!scroll_win)
  193.       open_scroller();
  194.       
  195.       /* critical section for size changes */
  196.    ModifyIDCMP(scroll_win, scroll_win->IDCMPFlags | IDCMP_SIZEVERIFY);
  197.    handle_scroller(0);   /* handle size problems first */
  198.  
  199.    if (!scroll_win)     /* window may have closed on us... */
  200.       return;
  201.  
  202.       /* add the characters */
  203.    SetDrMd(scroll_win->RPort, JAM1);
  204.    SetWrMsk(scroll_win->RPort, background | text);
  205.    SetAPen(scroll_win->RPort, text);
  206.    Move(scroll_win->RPort, scroll_win->BorderLeft, 
  207.       scroll_win->Height - scroll_win->BorderBottom 
  208.     - font->tf_YSize + font->tf_Baseline);
  209.    max_length = scroll_win->Width - scroll_win->BorderLeft - scroll_win->BorderRight;
  210.    max_length /= font->tf_XSize;
  211.    if (max_length > 14 * 4)
  212.       max_length = 14 * 4;    /* line length = 14 * 4 */
  213.    Text(scroll_win->RPort, s, max_length);
  214.    
  215.       /* add the separation lines */
  216.    separation_lines(scroll_win->Height - scroll_win->BorderBottom 
  217.     - font->tf_YSize);
  218.       
  219.       /* and scroll *JUST* the characters */
  220.    SetWrMsk(scroll_win->RPort, 1);
  221.    ScrollRaster(scroll_win->RPort, 0, font->tf_YSize, 
  222.                   scroll_win->BorderLeft, scroll_win->BorderTop, 
  223.                   scroll_win->Width - scroll_win->BorderRight - 1,
  224.                   scroll_win->Height - scroll_win->BorderBottom - 1);
  225.    
  226.       /* end of critical section: allow resize again */
  227.    ModifyIDCMP(scroll_win, scroll_win->IDCMPFlags & ~IDCMP_SIZEVERIFY);
  228.    handle_scroller(0); 
  229.    }
  230.